package com.ptrans;

import java.io.File;
import java.io.IOException;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.regex.Matcher;
import java.util.regex.Pattern;

import android.app.Activity;
import android.content.Context;
import android.content.Intent;
import android.content.pm.PackageManager;
import android.content.pm.ResolveInfo;
import android.graphics.Bitmap;
import android.graphics.BitmapFactory;
import android.net.Uri;
import android.os.AsyncTask;
import android.os.Bundle;
import android.os.Environment;
import android.provider.MediaStore;
import android.util.Log;
import android.view.View;
import android.view.View.OnClickListener;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.Toast;

import com.ptrans.modele.User;
import com.ptrans.photo.AlbumStorageDirFactory;
import com.ptrans.photo.BaseAlbumDirFactory;
import com.ptrans.server.UserHandler;
import com.ptrans.utilities.CommonUtilities;

/**
 * THis activity represent the screen when the user takes his photo.
 * @author Jean
 *
 */
public class SetUserActivity extends Activity {
 
	private static final int ACTION_TAKE_PHOTO = 1;
	private static final String BITMAP_STORAGE_KEY = "viewbitmap";
	private static final String IMAGEVIEW_VISIBILITY_STORAGE_KEY = "imageviewvisibility";
	private ImageView mImageView;
	private Bitmap mImageBitmap;
	
	
	private String mCurrentPhotoPath;
	private String lastPhotoPath;
	private boolean isCaptured = false;
	
	private Context context;
	
	private User user;
	
	private EditText fieldName;

	private static final String JPEG_FILE_PREFIX = "IMG_";
	private static final String JPEG_FILE_SUFFIX = ".jpg";

	private AlbumStorageDirFactory mAlbumStorageDirFactory = null;
	
	/* Photo album for this application */
	private String getAlbumName() {
		return getString(R.string.album_name);
	}
	
	private File getAlbumDir() {
		File storageDir = null;

		if (Environment.MEDIA_MOUNTED.equals(Environment.getExternalStorageState())) {
			
			storageDir = mAlbumStorageDirFactory.getAlbumStorageDir(getAlbumName());

			if (storageDir != null) {
				if (! storageDir.mkdirs()) {
					if (! storageDir.exists()){
						Log.d("userPicture", "failed to create directory");
						return null;
					}
				}
			}
			
		} else {
			Log.v(getString(R.string.app_name), "External storage is not mounted READ/WRITE.");
		}
		
		return storageDir;
	}
	
	/**
	 * Create the image file
	 * @return File : the image file created
	 * @throws IOException
	 */
	private File createImageFile() throws IOException {
		// Create an image file name
		String timeStamp = new SimpleDateFormat("yyyyMMdd_HHmmss").format(new Date());
		String imageFileName = JPEG_FILE_PREFIX + timeStamp + "_";
		File albumF = getAlbumDir();
		File imageF = File.createTempFile(imageFileName, JPEG_FILE_SUFFIX, albumF);
		return imageF;
	}
	
	/**
	 * Set the photo file
	 * @return
	 * @throws IOException
	 */
	private File setUpPhotoFile() throws IOException {
		
		File f = createImageFile();
		mCurrentPhotoPath = f.getAbsolutePath();
		
		return f;
	}
	
	private void setPic() {
		/* Decode the JPEG file into a Bitmap */
		Bitmap bitmap = BitmapFactory.decodeFile(mCurrentPhotoPath);
		Bitmap resizedbitmap = Bitmap.createScaledBitmap(bitmap, 500, 500, true);
		
		/* Associate the Bitmap to the ImageView */
		mImageView.setImageBitmap(resizedbitmap);
		mImageView.setVisibility(View.VISIBLE);
		
		lastPhotoPath = mCurrentPhotoPath;
		isCaptured = true;
		
	}

	private void galleryAddPic() {
		    Intent mediaScanIntent = new Intent("android.intent.action.MEDIA_SCANNER_SCAN_FILE");
			File f = new File(mCurrentPhotoPath);
		    Uri contentUri = Uri.fromFile(f);
		    mediaScanIntent.setData(contentUri);
		    this.sendBroadcast(mediaScanIntent);
	}

	
	private void dispatchTakePictureIntent(int actionCode) {

		Intent takePictureIntent = new Intent(MediaStore.ACTION_IMAGE_CAPTURE);

		switch(actionCode) {
		case ACTION_TAKE_PHOTO:
			File f = null;
			
			try {
				f = setUpPhotoFile();
				mCurrentPhotoPath = f.getAbsolutePath();
				takePictureIntent.putExtra(MediaStore.EXTRA_OUTPUT, Uri.fromFile(f));
			} catch (IOException e) {
				e.printStackTrace();
				f = null;
				mCurrentPhotoPath = null;
			}
			break;

		default:
			break;			
		} // switch

		startActivityForResult(takePictureIntent, actionCode);
	}

	private void handleBigCameraPhoto() {

		if (mCurrentPhotoPath != null) {
			setPic();
			galleryAddPic();
			mCurrentPhotoPath = null;
		}

	}
	
	private OnClickListener btnValidateListener = new OnClickListener() {
		@Override
		public void onClick(View v) {
			Pattern p = Pattern.compile("[^a-z0-9 ]", Pattern.CASE_INSENSITIVE);
			Matcher m = p.matcher(fieldName.getText().toString());
			boolean b = m.find();
			
			if(!isCaptured) {
				Toast.makeText(getApplicationContext(), getString(R.string.no_photo_captured), Toast.LENGTH_SHORT).show();
			} else if(fieldName.getText().toString().equals("")) {
				Toast.makeText(getApplicationContext(), getString(R.string.no_name), Toast.LENGTH_SHORT).show();
			} else if(fieldName.getText().toString().contains(" ")) {
				Toast.makeText(getApplicationContext(), getString(R.string.there_is_espace), Toast.LENGTH_SHORT).show();
			} else if(b) {
				Toast.makeText(getApplicationContext(), getString(R.string.there_is_special_char), Toast.LENGTH_SHORT).show();
			} else {
				user.setName(fieldName.getText().toString());
				user.setPicture(lastPhotoPath);
				
				checkUsernameInBackground();
			}
		}
	};
	
	Button.OnClickListener mTakePicOnClickListener = 
		new Button.OnClickListener() {
		@Override
		public void onClick(View v) {
			dispatchTakePictureIntent(ACTION_TAKE_PHOTO);
		}
	};
	
	@Override
	public void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
		setContentView(R.layout.photo);
		
		context = getApplicationContext();
		user = new User();
		
		mImageView = (ImageView) findViewById(R.id.imgPreview);
		mImageBitmap = null;

		Button picBtn = (Button) findViewById(R.id.btnCapturePicture);
		setBtnListenerOrDisable( 
				picBtn, 
				mTakePicOnClickListener,
				MediaStore.ACTION_IMAGE_CAPTURE
		);
		
		Button btnValidate = (Button) findViewById(R.id.btnValidate);
		btnValidate.setOnClickListener(btnValidateListener);
		
		fieldName = (EditText)findViewById(R.id.fieldname);
		
		mAlbumStorageDirFactory = new BaseAlbumDirFactory();
	}
	
	 private void checkUsernameInBackground() {
		    new AsyncTask<Object, Object, Boolean>() {
		    	
		    	protected Boolean doInBackground(Object... params) {
		    		String msg = "";
		    		Boolean b;
		    		b = UserHandler.isNameExist(context, user);
					if(b.booleanValue()) msg = getString(R.string.name_not_exists);
					else {
						msg = getString(R.string.name_exists);
					}
	    			Log.i(CommonUtilities.TAG, msg);
	    			return b;
	    		}
	    		
    		protected void onPostExecute(Boolean b) {
            	if(b.booleanValue()) {
            		Toast.makeText(getApplicationContext(), getString(R.string.username_checked), Toast.LENGTH_SHORT).show();
            		// Go back to HOME ACTIVITY
            		Intent returnIntent = new Intent();
					returnIntent.putExtra(CommonUtilities.EXTRA_USER,user);
					setResult(RESULT_OK,returnIntent);     
					finish();
            	}
            	else {
            		Toast.makeText(getApplicationContext(), getString(R.string.username_checked_error), Toast.LENGTH_SHORT).show();
            	}
    		}
    	}.execute(null, null, null);
    }
	
	@Override
	protected void onActivityResult(int requestCode, int resultCode, Intent data) {
		switch (requestCode) {
			case ACTION_TAKE_PHOTO: {
				if (resultCode == RESULT_OK) {
					handleBigCameraPhoto();
				}
				break;
			} // ACTION_TAKE_PHOTO_B
		} // switch
	}
	
	// Some lifecycle callbacks so that the image can survive orientation change
	@Override
	protected void onSaveInstanceState(Bundle outState) {
		outState.putParcelable(BITMAP_STORAGE_KEY, mImageBitmap);
		outState.putBoolean(IMAGEVIEW_VISIBILITY_STORAGE_KEY, (mImageBitmap != null) );
		super.onSaveInstanceState(outState);
	}
	
	@Override
	protected void onRestoreInstanceState(Bundle savedInstanceState) {
		super.onRestoreInstanceState(savedInstanceState);
		mImageBitmap = savedInstanceState.getParcelable(BITMAP_STORAGE_KEY);
		mImageView.setImageBitmap(mImageBitmap);
		mImageView.setVisibility(
				savedInstanceState.getBoolean(IMAGEVIEW_VISIBILITY_STORAGE_KEY) ? 
						ImageView.VISIBLE : ImageView.INVISIBLE
		);
	}
	
	/**
	 * Indicates whether the specified action can be used as an intent. This
	 * method queries the package manager for installed packages that can
	 * respond to an intent with the specified action. If no suitable package is
	 * found, this method returns false.
	 * http://android-developers.blogspot.com/2009/01/can-i-use-this-intent.html
	 *
	 * @param context The application's environment.
	 * @param action The Intent action to check for availability.
	 *
	 * @return True if an Intent with the specified action can be sent and
	 *         responded to, false otherwise.
	 */
	public static boolean isIntentAvailable(Context context, String action) {
		final PackageManager packageManager = context.getPackageManager();
		final Intent intent = new Intent(action);
		List<ResolveInfo> list =
			packageManager.queryIntentActivities(intent,
					PackageManager.MATCH_DEFAULT_ONLY);
		return list.size() > 0;
	}

	private void setBtnListenerOrDisable( 
			Button btn, 
			Button.OnClickListener onClickListener,
			String intentName
	) {
		if (isIntentAvailable(this, intentName)) {
			btn.setOnClickListener(onClickListener);        	
		} else {
			btn.setText( 
				getText(R.string.cannot).toString() + " " + btn.getText());
			btn.setClickable(false);
		}
	}


	
}
